﻿using ArcGIS.Core.CIM;
using ArcGIS.Core.Data;
using ArcGIS.Core.Geometry;
using ArcGIS.Core.Internal.CIM;
using ArcGIS.Desktop.Core;
using ArcGIS.Desktop.Framework.Threading.Tasks;
using ArcGIS.Desktop.Internal.Framework.Utilities;
using ArcGIS.Desktop.Layouts;
using ArcGIS.Desktop.Mapping;
using Aspose.Cells;
using Aspose.Words;
using CCTool.Scripts.Manager;
using CCTool.Scripts.ToolManagers;
using CCTool.Scripts.ToolManagers.Extensions;
using CCTool.Scripts.ToolManagers.Managers;
using MathNet.Numerics;
using MathNet.Numerics.LinearAlgebra.Factorization;
using NPOI.POIFS.Crypt.Dsig;
using NPOI.SS.Formula.Functions;
using NPOI.SS.Formula.PTG;
using NPOI.SS.UserModel;
using NPOI.SS.Util;
using NPOI.XSSF.UserModel;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Forms;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using static System.Net.Mime.MediaTypeNames;
using System.Xml.Linq;
using MessageBox = System.Windows.Forms.MessageBox;
using Polygon = ArcGIS.Core.Geometry.Polygon;
using QueryFilter = ArcGIS.Core.Data.QueryFilter;
using Range = Aspose.Cells.Range;
using SpatialReference = ArcGIS.Core.Geometry.SpatialReference;
using TextElement = ArcGIS.Desktop.Layouts.TextElement;
using NPOI.Util;
using System.Security.Cryptography;
using static System.Runtime.InteropServices.JavaScript.JSType;
using Aspose.Cells.Drawing;
using Envelope = ArcGIS.Core.Geometry.Envelope;
using SharpCompress.Common;
using System.Runtime.Intrinsics.Arm;

namespace CCTool.Scripts.CusTool4
{
    /// <summary>
    /// Interaction logic for CreateNYDT.xaml
    /// </summary>
    public partial class CreateNYDT : ArcGIS.Desktop.Framework.Controls.ProWindow
    {
        // 工具设置标签
        readonly string toolSet = "CreateNYDT";
        public CreateNYDT()
        {
            InitializeComponent();

            // 初始化参数选项
            textFolderPath.Text = BaseTool.ReadValueFromReg(toolSet, "outFolder");
            textBM.Text = BaseTool.ReadValueFromReg(toolSet, "bm", "江苏省农垦集团农用地调查表");
            textCZF.Text = BaseTool.ReadValueFromReg(toolSet, "czf", "江苏省农垦农业发展股份有限公司淮海分公司");
            textBZ.Text = BaseTool.ReadValueFromReg(toolSet, "bz", "该调查成果将用于淮海农场土地详查数据库建设。");
            textScale.Text = BaseTool.ReadValueFromReg(toolSet, "sca", "1");
        }

        // 更新默认字段
        public async void UpdataField()
        {
            string ly = combox_fc.ComboxText();

            // 初始化参数选项
            await UITool.InitLayerFieldToComboxPlus(combox_fcmc, ly, "SCQMC", "string");
            await UITool.InitLayerFieldToComboxPlus(combox_ddmc, ly, "DDMC", "string");
            await UITool.InitLayerFieldToComboxPlus(combox_tth, ly, "NFBH", "string");
            await UITool.InitLayerFieldToComboxPlus(combox_bh, ly, "TBBH", "string");
            await UITool.InitLayerFieldToComboxPlus(combox_mj, ly, "TBMJM", "float");

        }


        // 定义一个进度框
        private ProcessWindow processwindow = null;
        string tool_name = "批量生成农用地调查表(弓)";

        private void combox_fc_DropDown(object sender, EventArgs e)
        {
            UITool.AddFeatureLayersToComboxPlus(combox_fc);
        }

        private void openFolderButton_Click(object sender, RoutedEventArgs e)
        {
            textFolderPath.Text = UITool.OpenDialogFolder();
        }

        // 获取字段值，如无则为""
        private string GetFieldValue(Feature feature, string fieldName)
        {
            string result = "";

            if (fieldName is not null && fieldName != "")
            {
                result = feature[fieldName]?.ToString();

                if (fieldName is null)
                {
                    result = "";
                }
            }

            return result;
        }


        private async void btn_go_Click(object sender, RoutedEventArgs e)
        {
            try
            {
                string defGDB = Project.Current.DefaultGeodatabasePath;

                // 参数获取
                string in_fc = combox_fc.ComboxText();
                string outFolder = textFolderPath.Text;


                string field_fcmc = combox_fcmc.ComboxText();
                string field_ddmc = combox_ddmc.ComboxText();
                string field_tth = combox_tth.ComboxText();
                string field_bh = combox_bh.ComboxText();
                string field_mj = combox_mj.ComboxText();

                string bm = textBM.Text;
                string czf = textCZF.Text;
                string bz = textBZ.Text;

                double sca = textScale.Text.ToDouble();

                // 判断参数是否选择完全
                if (in_fc == "" || outFolder == "")
                {
                    MessageBox.Show("有必选参数为空！！！");
                    return;
                }

                // 写入本地
                BaseTool.WriteValueToReg(toolSet, "outFolder", outFolder);
                BaseTool.WriteValueToReg(toolSet, "bm", bm);
                BaseTool.WriteValueToReg(toolSet, "czf", czf);
                BaseTool.WriteValueToReg(toolSet, "bz", bz);
                BaseTool.WriteValueToReg(toolSet, "sca", sca);

                // 打开进度框
                ProcessWindow pw = UITool.OpenProcessWindow(processwindow, tool_name);
                pw.AddMessageTitle(tool_name);

                Close();

                await QueuedTask.Run(() =>
                {
                    // 获取目标FeatureLayer
                    FeatureLayer featurelayer = in_fc.TargetFeatureLayer();

                    // 创建文件夹
                    string targetFolder = $@"{outFolder}\{featurelayer.Name}";
                    DirTool.CreateFolder(targetFolder);

                    // 出图
                    // 获取LayoutProjectItem
                    string layoutName = "农用地调查图";
                    LayoutProjectItem layoutItem = Project.Current.GetItems<LayoutProjectItem>().FirstOrDefault(item => item.Name.Equals(layoutName));
                    Layout layout = layoutItem.GetLayout();            // 获取Layout                         
                    MapFrame mf = layout.FindElement("地图框") as MapFrame;             // 获取主地图框
                    Map map = mf.Map;                         // 获取主地图

                    FeatureLayer zdLayer = map.GetLayersAsFlattenedList().FirstOrDefault(l => l.Name == "测试数据") as FeatureLayer;

                    SpatialReference sr = zdLayer.GetSpatialReference();
                    // 更新地图坐标系
                    map.SetSpatialReference(sr);
                    // 更新图层的源
                    string fcPath = in_fc.TargetLayerPath();
                    GisTool.UpdataLayerSource(zdLayer, fcPath);


                    // 遍历面要素类中的所有要素
                    using RowCursor rowCursor = zdLayer.Search();
                    while (rowCursor.MoveNext())
                    {
                        using var feature = rowCursor.Current as Feature;
                        Polygon polygon = feature.GetShape() as Polygon;

                        // 获取多边形的质心
                        MapPoint centroid = GeometryEngine.Instance.Centroid(polygon);

                        // 获取质心的XY坐标值
                        double x = centroid.X;
                        double y = centroid.Y;

                        // 获取参数
                        long oid = feature.GetObjectID();
                        string oidField = zdLayer.TargetIDFieldName();


                        string fcmc = GetFieldValue(feature, field_fcmc);
                        string ddmc = GetFieldValue(feature, field_ddmc);
                        string tth = GetFieldValue(feature, field_tth);
                        string bh = GetFieldValue(feature, field_bh);
                        string mj = GetFieldValue(feature, field_mj);

                        pw.AddMessageMiddle(5, $"处理要素：{oid} - 条田号：{tth}");


                        // 更新文本标签
                        UpdataText(layout, "图名", $"{bm}");
                        UpdataText(layout, "备注", $"备注：{bz}");
                        UpdataText(layout, "分场名称", $"{fcmc}");
                        UpdataText(layout, "耕地地块条田号", $"{tth}");
                        UpdataText(layout, "调查编号", $"{bh}");

                        UpdataText(layout, "大队名称", $"{ddmc}");
                        UpdataText(layout, "调查面积", $"{mj.ToDouble().RoundWithFill(2)}");
                        UpdataText(layout, "耕地地块承租方", $"{czf}");

                        UpdataText(layout, "x坐标", $"{x.RoundWithFill(4)}");
                        UpdataText(layout, "y坐标", $"{y.RoundWithFill(4)}");


                        mf.SetCamera(feature.GetShape().Extent);

                        // 可以调节缩放
                        Camera cam = mf.Camera;
                        double sc = cam.Scale * sca;
                        cam.Scale = sc;
                        mf.SetCamera(cam);

                        // 只显示当前要素
                        zdLayer.SetDefinitionQuery($"{oidField} = {oid}");

                        // PDF图片属性
                        PDFFormat PDF = new PDFFormat()
                        {
                            OutputFileName =  $@"{targetFolder}\{tth}.pdf",      // 输出路径
                            Resolution = 300,               // 分辨率
                            DoCompressVectorGraphics = true,   // 是否压缩矢量图形
                            DoEmbedFonts = true,            // 是否执行嵌入字体         
                            HasGeoRefInfo = true,             // 是否具有地理参考信息
                            ImageCompression = ImageCompression.Adaptive,   // 图形压缩.自适应
                            ImageQuality = ImageQuality.Best,           // 图形质量
                            LayersAndAttributes = LayersAndAttributes.LayersAndAttributes,   // 图层  属性
                        };

                        // 导出图片
                        layout.Export(PDF);

                        // 恢复定义
                        zdLayer.RemoveAllDefinitionQueries();
                    }

                    pw.AddMessageEnd();
                });
            }
            catch (Exception ee)
            {
                MessageBox.Show(ee.Message + ee.StackTrace);
                return;
            }
        }



        private void btn_help_Click(object sender, RoutedEventArgs e)
        {
            string url = "https://blog.csdn.net/xcc34452366/article/details/149605044";
            UITool.Link2Web(url);
        }


        private void combox_fc_DropClose(object sender, EventArgs e)
        {
            // 更新默认字段
            UpdataField();
        }



        // 更新文本标签
        private static void UpdataText(Layout layout, string name, string text)
        {
            TextElement te = layout.FindElement(name) as TextElement;

            var a = te.TextProperties;
            te.SetTextProperties(new TextProperties(text, a.Font, a.FontSize, a.FontStyle));
        }


        // 自适应设置比例
        public static double SetScaleCus(double scale)
        {
            double targetScale = scale;

            List<long> scales = new List<long> { 100, 200, 300, 500, 1000, 2000, 3000, 4000, 5000, 8000, 10000, 20000 };

            foreach (long s in scales)
            {
                if (scale < s)
                {
                    targetScale = s;
                    break;
                }
            }

            return targetScale;

        }

        private void combox_mj_DropDown(object sender, EventArgs e)
        {
            UITool.AddFloatFieldsToComboxPlus(combox_fc.ComboxText(), combox_mj);
        }

        private void combox_bh_DropDown(object sender, EventArgs e)
        {
            UITool.AddTextFieldsToComboxPlus(combox_fc.ComboxText(), combox_bh);
        }

        private void combox_tth_DropDown(object sender, EventArgs e)
        {
            UITool.AddTextFieldsToComboxPlus(combox_fc.ComboxText(), combox_tth);
        }

        private void combox_ddmc_DropDown(object sender, EventArgs e)
        {
            UITool.AddTextFieldsToComboxPlus(combox_fc.ComboxText(), combox_ddmc);
        }

        private void combox_fcmc_DropDown(object sender, EventArgs e)
        {
            UITool.AddTextFieldsToComboxPlus(combox_fc.ComboxText(), combox_fcmc);
        }

    }
}
